package com.mindainfo.groundwave.server.member.service;

import com.mindainfo.groundwave.common.api.member.param.*;
import com.mindainfo.groundwave.common.api.member.service.IDeptService;
import com.mindainfo.groundwave.common.api.member.vo.DeptGetDeptInfoVo;
import com.mindainfo.groundwave.common.api.member.vo.DeptGetMyDeptsVo;
import com.mindainfo.groundwave.common.api.member.vo.DeptQueryListVo;
import com.mindainfo.groundwave.common.bean.*;
import com.mindainfo.groundwave.server.member.bean.SysDept;
import com.mindainfo.groundwave.server.member.bean.SysDeptInfo;
import com.mindainfo.groundwave.server.member.bean.SysMember;
import com.mindainfo.groundwave.server.member.mapper.SysDeptInfoMapper;
import com.mindainfo.groundwave.server.member.mapper.SysDeptMapper;
import org.apache.logging.log4j.core.util.datetime.FastDateFormat;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.session.Session;
import org.apache.shiro.subject.Subject;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.StringUtils;

import javax.annotation.Resource;
import java.util.*;

/**
 * Created by MD-01 on 2017/5/16.
 */
@Service
@Transactional
public class DeptServiceImpl implements IDeptService{

    @Resource
    private SysDeptMapper deptMapper;
    @Resource
    private SysDeptInfoMapper deptInfoMapper;

    /**
     * 页面分页获取部门列表
     */
    public CommonResult<TableData<DeptQueryListVo>> queryList(DeptQueryListParam param) {


        Subject subject = SecurityUtils.getSubject();
        Session session = subject.getSession();
        SysMember member = (SysMember) session.getAttribute("member");

        List<SysDept> myDepts = getMyDeptList(member.getDeptId());

        //存放条件查询后的数据
        List<SysDept> queryDepts = new ArrayList<>();
        for(SysDept dept : myDepts){
            if(!StringUtils.isEmpty(param.getKey())){
                if(!dept.getName().contains(param.getKey())){
                    continue;
                }
            }
            queryDepts.add(dept);
        }
        int count = queryDepts.size();

        //分页
        int start = param.getStart();
        int end = param.getStart() + param.getNum();

        List<DeptQueryListVo> vos = new ArrayList<>();
        FastDateFormat format = FastDateFormat.getInstance("yyyy-MM-dd HH:mm:ss");
        for(int i=0;i<count;i++){
            if(i>=start && i<end){
                DeptQueryListVo vo = new DeptQueryListVo();
                SysDept dept = queryDepts.get(i);
                vo.setDeptId(dept.getId());
                vo.setName(dept.getName());
                vo.setManagerName(dept.getManagerName());
                vo.setManagerPhone(dept.getManagerPhone());
                vo.setParentId(dept.getParentId());
                vo.setCreateTime(format.format(dept.getCreateTime()));
                SysDept parent = deptMapper.selectById(dept.getParentId());
                if(parent!=null){
                    vo.setParentName(parent.getName());
                }
                SysDeptInfo deptInfo = deptInfoMapper.get(dept.getId());
                if(deptInfo==null){
                    vo.setInfo(0);
                }else{
                    vo.setInfo(1);
                }
                vos.add(vo);
            }
        }
        TableData<DeptQueryListVo> data = new TableData<>();
        data.setRecordsFiltered(count);
        data.setRecordsTotal(count);
        data.setData(vos);
        return ResultFactory.ok(data);
    }

    /**
     * 页面添加部门
     */
    public CommonResult<Void> save(DeptSaveParam param) {
        if(StringUtils.isEmpty(param.getManagerName())){
            return ResultFactory.error("组织联系人不能为空");
        }
        if(StringUtils.isEmpty(param.getManagerPhone())){
            return ResultFactory.error("组织联系人电话不能为空");
        }
        if(StringUtils.isEmpty(param.getName())){
            return ResultFactory.error("组织名称不能为空");
        }
        if(param.getParentId()==null){
            return ResultFactory.error("上级组织编号不能为空");
        }
        //新建
        if(param.getDeptId()==null){
            SysDept dept = deptMapper.queryByName(param.getName());
            if(dept!=null){
                return ResultFactory.error("组织名称已经存在");
            }
            dept = new SysDept();
            dept.setParentId(param.getParentId());
            dept.setName(param.getName());
            dept.setCreateTime(new Date());
            dept.setManagerName(param.getManagerName());
            dept.setManagerPhone(param.getManagerPhone());
            deptMapper.insert(dept);

            //新增部门后,清除session中的部门列表
            Subject subject = SecurityUtils.getSubject();
            Session session = subject.getSession();
            session.removeAttribute("myDeptList");

            return ResultFactory.ok();
        }
        //修改
        SysDept dept = deptMapper.selectById(param.getDeptId());
        if(dept==null){
            return ResultFactory.error("错误的组织编号");
        }
        dept.setManagerPhone(param.getManagerPhone());
        dept.setManagerName(param.getManagerName());
        dept.setName(param.getName());
        dept.setParentId(param.getParentId());
        deptMapper.updateById(dept);

        //修改部门后,清除session中的部门列表
        Subject subject = SecurityUtils.getSubject();
        Session session = subject.getSession();
        session.removeAttribute("myDeptList");

        return ResultFactory.ok();
    }


    /**
     * 删除部门
     */
    public CommonResult<Void> toDel(DeptTodelParam param){
        SysDept dept = deptMapper.selectById(param.getDeptId());
        if(dept==null){
            return ResultFactory.error("错误的组织编号");
        }
        List<SysDept> sysDepts = deptMapper.queryByParentId(dept.getId());
        if(sysDepts.size()>0){
            return ResultFactory.error("该组织有下级组织,不能删除");
        }
        deptMapper.deleteById(param.getDeptId());

        //删除部门后,清除session中的部门列表
        Subject subject = SecurityUtils.getSubject();
        Session session = subject.getSession();
        session.removeAttribute("myDeptList");

        return ResultFactory.ok();
    }

    /**
     * 根据部门id获取该部门和其所有的下属部门
     */
    public CommonResult<List<DeptGetMyDeptsVo>> getMyDepts() {

        Subject subject = SecurityUtils.getSubject();
        Session session = subject.getSession();

        //先从session中获取
        List<SysDept> depts = (List<SysDept>) session.getAttribute("myDeptList");
        if(depts==null){
            SysMember member = (SysMember) session.getAttribute("member");
            depts = getMyDeptList(member.getDeptId());
            session.setAttribute("myDeptList",depts);
        }

        List<DeptGetMyDeptsVo> vos = new ArrayList<>();
        for(SysDept dept : depts){
            DeptGetMyDeptsVo vo = new DeptGetMyDeptsVo();
            vo.setDeptId(dept.getId());
            vo.setName(dept.getName());
            vo.setParentId(dept.getParentId());
            vos.add(vo);
        }
        return ResultFactory.ok(vos);
    }

    /**
     * 获取当前用户部门树id的list
     */
    public CommonResult<List<Integer>> getMyDeptIdList() {

        CommonResult<List<DeptGetMyDeptsVo>> myDepts = getMyDepts();
        List<Integer> idList = new ArrayList<>();
        for (DeptGetMyDeptsVo vo : myDepts.getData()){
            idList.add(vo.getDeptId());
        }
        return ResultFactory.ok(idList);
    }

    /**
     * 设置部门属性
     */
    public CommonResult<Void> setDeptInfo(DeptSetDeptInfoParam param){

        SysDeptInfo deptInfo = deptInfoMapper.get(param.getDeptId());
        if(deptInfo==null){
            deptInfo = new SysDeptInfo();
            deptInfo.setDeptId(param.getDeptId());
            deptInfoMapper.insert(deptInfo);
        }
        deptInfo.setCreateTime(new Date());
        deptInfo.setLat(param.getLat());
        deptInfo.setLng(param.getLng());
        deptInfo.setName(param.getName());
        deptInfo.setZoom(param.getZoom());
        deptInfoMapper.updateById(deptInfo);
        return ResultFactory.ok();
    }

    /**
     * 获取部门属性
     */
    public CommonResult<DeptGetDeptInfoVo> getDeptInfo(DeptGetDeptInfoParam param){
        SysDeptInfo deptInfo = deptInfoMapper.get(param.getDeptId());
        if(deptInfo==null){
            return ResultFactory.error("暂时没有部门属性");
        }
        DeptGetDeptInfoVo vo = new DeptGetDeptInfoVo();
        vo.setDeptId(deptInfo.getDeptId());
        vo.setLat(deptInfo.getLat());
        vo.setLng(deptInfo.getLng());
        vo.setName(deptInfo.getName());
        vo.setZoom(deptInfo.getZoom());
        return ResultFactory.ok(vo);
    }


    /**
     * 根据部门id获取该部门和其所有的下属部门
     */
    private List<SysDept> getMyDeptList(Integer deptId){

        List<SysDept> deptList = new ArrayList<>();

        //先获取所有的部门树
        Tree<SysDept> deptTree = getDeptTree();

        //根据部门编号获取子树
        Tree<SysDept> tree = memberDepts(deptTree, deptId);

        if(tree!=null){
            //将自己的部门树转换成list
            createMyDepts(tree,deptList);
        }
        return deptList;
    }

    /**
     * 将自己的部门树转换成list
     * @param tree
     * @param deptList
     */
    private void createMyDepts(Tree<SysDept> tree,List<SysDept> deptList){
        SysDept data = tree.getData();
        deptList.add(data);
        List<Tree<SysDept>> children = tree.getChildren();
        if(children!=null && children.size()!=0){
            for(Tree<SysDept> child : tree.getChildren()){
                createMyDepts(child,deptList);
            }
        }
    }


    /**
     * 获取自己所在部门的部门树
     * 自己的deptId 为顶层树
     */
    private Tree<SysDept> memberDepts(Tree<SysDept> tree, Integer deptId){
        if(tree.getData().getId()==deptId){
            return tree;
        }else{
            List<Tree<SysDept>> children = tree.getChildren();
            if(children!=null && children.size()!=0){
                for(Tree<SysDept> child : children){
                    Tree<SysDept> memberTree = memberDepts(child, deptId);
                    if(memberTree!=null){
                        return memberTree;
                    }
                }
            }
        }
        return null;
    }

    /**
     * 获取所有部门组成的部门树
     */
    private Tree<SysDept> getDeptTree(){
        List<SysDept> deptList = deptMapper.queryAll();
        Tree<SysDept> tree = new Tree<>();
        createDeptTree(deptList,tree);
        return tree;
    }

    /**
     * 构建部门树
     */
    private void createDeptTree(List<SysDept> deptList,Tree<SysDept> tree){
        if(tree.getData()==null){
            for(SysDept dept : deptList){
                if(dept.getParentId()==0){
                    tree.setData(dept);
                    break;
                }
            }
            createDeptTree(deptList,tree);
        }else{
            for(SysDept dept : deptList){
                if(dept.getParentId()==tree.getData().getId()){
                    Tree<SysDept> child = new Tree<>();
                    child.setData(dept);
                    tree.getChildren().add(child);
                    createDeptTree(deptList,child);
                }
            }
        }
    }

}
